﻿using AhCha.Fortunate.Api.Controllers.MSSQL;
using System.Text;
using AhCha.Fortunate.Common.Extensions;
using AhCha.Fortunate.Common.Const;
using AhCha.Fortunate.Common.Global;
using AhCha.Fortunate.IService.MySQL;
using AhCha.Fortunate.ModelsDto.MySQL.ApiRequestLogDto;

using Newtonsoft.Json;
using System.Net;
using Microsoft.AspNetCore.Diagnostics;
using Microsoft.AspNetCore.Mvc;
using AhCha.Fortunate.ModelsDto;
using AhCha.Fortunate.Api.Controllers;

//中间件
namespace AhCha.Fortunate.Api.AppCode
{

    /// <summary>
    /// 中间件获取token数据
    /// </summary>
    public class TokenMiddleware
    {
        private readonly RequestDelegate _next;
        public TokenMiddleware(RequestDelegate next)
        {
            _next = next;
        }
        public async Task InvokeAsync(HttpContext context)
        {
            //验证
            if (context.User.Identity.IsAuthenticated)
            {   //可获取token数据
                //CurrentUser.GetUserId = long.Parse(context.User.FindFirst(ClaimConst.CLAINM_USERID)?.Value ?? "0");
                //CurrentUser.GetUserRoleId = long.Parse(context.User.FindFirst(ClaimConst.CLAINM_ROLE_ID)?.Value ?? "0");
                //CurrentUser.GetUserRoleName = context.User.FindFirst(ClaimConst.CLAINM_ROLE_Name)?.Value;
                //CurrentUser.GetUserName = context.User.FindFirst(ClaimConst.CLAINM_NAME)?.Value;
                //CurrentUser.GetUserAccount = context.User.FindFirst(ClaimConst.CLAINM_ACCOUNT)?.Value;
                //CurrentUser.GetUserDeviceId = context.User.FindFirst(ClaimConst.CLAINM_DEVICE_ID)?.Value;
            }
            await _next(context);
        }
    }

    /// <summary>
    /// 中间件 - 接口请求记录日志
    /// </summary>
    public class RequestMiddleware
    {
        private readonly RequestDelegate _next;
        public RequestMiddleware(RequestDelegate next)
        {
            _next = next;
        }
        public async Task InvokeAsync(HttpContext context)
        {
            //是否已通过验证
            if (context.User.Identity.IsAuthenticated)
            {
                string ControllerName = context.Request.RouteValues["Controller"].ToString();
                string ActionName = context.Request.RouteValues["Action"].ToString();
                if (!typeof(LogController).Name.StartsWith(ControllerName) && !typeof(SysFileController).Name.StartsWith(ControllerName) && !context.Request.HasFormContentType)
                {
                    string InputParams = string.Empty;
                    if (context.Request.Method == "GET")
                    {
                        if (context.Request.Query.Count() > 0)
                        {
                            Dictionary<string, string> inputs = new Dictionary<string, string>();
                            foreach (var item in context.Request.Query)
                            {
                                inputs.Add(item.Key, item.Value);
                            }
                            InputParams = JsonConvert.SerializeObject(inputs);
                        }
                    }
                    if (context.Request.Method == "POST" || context.Request.Method == "PUT" || context.Request.Method == "DELETE")
                    {
                        var isFileUpload = context.Request.HasFormContentType;
                        if (!isFileUpload)
                        {
                            // 启用缓冲和重置功能，以便多次读取请求体
                            context.Request.EnableBuffering();
                            using (var reader = new StreamReader(context.Request.Body, Encoding.UTF8, true, 1024, true))
                            {
                                InputParams = await reader.ReadToEndAsync();
                            }
                            // 将读取器重置回流的开头，以便下一个中间件或控制器可以读取它
                            context.Request.Body.Position = 0;
                        }
                    }
                    InputParams = string.IsNullOrWhiteSpace(InputParams) ? "无输入参数" : InputParams;
                    #region 添加MySql梦数据库
                    IApiRequestLogService apiRequestLogService = AhChaFortunateGlobalContext.GetService<IApiRequestLogService>();
                    PostApiRequestLogInput entity = new PostApiRequestLogInput()
                    {
                        ControllerName = ControllerName,
                        ActionName = ActionName,
                        Method = context.Request.Method,
                        Ip = context.GetIp(),
                        Param = InputParams,
                        Host = context.Request.Host.ToString(),
                        Path = context.Request.Path,
                    };
                    await apiRequestLogService.PostApiRequestLog(entity);
                    #endregion
                }
            }
            await _next(context);
        }
    }

    /// <summary>
    /// IApplicationBuilder扩展
    /// </summary>
    public static class FortunateMiddlewareExtensions
    {
        /// <summary>
        /// 中间件 - 获取Token
        /// </summary>
        public static IApplicationBuilder UseCurrentToken(this IApplicationBuilder builder)
        {
            return builder.UseMiddleware<TokenMiddleware>();
        }

        /// <summary>
        /// 中间件 - 接口请求记录日志
        /// </summary>
        public static IApplicationBuilder UseRequestMiddleware(this IApplicationBuilder builder)
        {
            return builder.UseMiddleware<RequestMiddleware>();
        }
    }

}
